
#include "timelineInspector.h"
#include "renderer.h"
#include "input.h"
#include "skeletalActor.h"

//this inspector does not remove its buttons when closed!
TimelineInspector::TimelineInspector(){

    bOpen=false;
    initialLocation=location;
    tabHeight=(renderer->screenY * 0.3f);
    listHeight=15;
    listWidth=40;
    level=0;
    timeScale=.1f;
}

TimelineInspector::~TimelineInspector(){}


void TimelineInspector::setup(){
Button::setup();

}

void TimelineInspector::update(double deltaTime)
{
    // temporary: set button to display zoom level
    stringstream sst;
    sst << timeScale;
    if( listButton.size() > 5 ) listButton[5]->name.assign(sst.str());

    // check delete timeline
    if( input->lastKey == 127 || input->lastKey == 8 )
        for(uint i=0;i<listButton.size();i++)
            if (listButton[i]==input->hudTarget && (i-6)%3==0)
                removeTimeline(i);
}

void TimelineInspector::drawPlane(){

    Button::drawPlane();

    renderer->setupShading("color");
    if (bOpen){
        renderer->drawPlane(scale.x,0.0, renderer->screenX,renderer->screenY, Vector4f(0.4,0.4,0.4, 1.0));
    }
}

void TimelineInspector::mouseOver(){

    Button::mouseOver();
}

void TimelineInspector::mouseDrag(){}

void TimelineInspector::clickedLeft(){


    if (!bOpen){
        initialLocation=location;
        location.y-=tabHeight;
        bOpen=true;
        for (uint i=0;i<listButton.size();i++)
            {
            listButton[i]->location.y-=tabHeight;
            listButton[i]->initialLocation.y=listButton[i]->location.y;
            }
       ListButton::clickedLeft();
       placeTimelineButtons();
     }
    else{
        for (uint i=0;i<listButton.size();i++)
            listButton[i]->location.y+=initialLocation.y-location.y;
        location=initialLocation;
        placeTimelineButtons();
        bOpen=false;
    }

}



void TimelineInspector::assembleList(){

    if (bOpen){
        cout << "creating list..." << endl;

        cout << "timelineActors size: " << timelineActors.size() << endl;

        //create AddActor Button
            renderer->actorInfo["14GetActorButton"].actorReference->create();
            listButton.push_back(renderer->buttonList.back());

            listButton[0]->name="getActor";
            listButton[0]->parent=this;
            listButton[0]->level=level+1;
            listButton[0]->tooltip="";
            listButton[0]->color=Vector4f(0.6,0.3,0.3,1.0);
            listButton[0]->bPermanent=true;
            listButton[0]->bDrawName=true;
            listButton[0]->name="Add";
            listButton[0]->sceneShaderID="color";
            listButton[0]->setup();


            renderer->actorInfo["12AssignButton"].actorReference->create();
            listButton.push_back(renderer->buttonList.back());

            listButton[1]->name="play";
            listButton[1]->bDrawName=true;
            listButton[1]->parent=this;
            listButton[1]->level=level+1;
            listButton[1]->tooltip="";
            listButton[1]->color=Vector4f(0.3,0.6,0.3,1.0);
            listButton[1]->bPermanent=true;
            listButton[1]->sceneShaderID="color";
            listButton[1]->setup();


            renderer->actorInfo["12AssignButton"].actorReference->create();
            listButton.push_back(renderer->buttonList.back());

            listButton[2]->name="pause";
            listButton[2]->bDrawName=true;
            listButton[2]->parent=this;
            listButton[2]->level=level+1;
            listButton[2]->tooltip="";
            listButton[2]->color=Vector4f(0.3,0.6,0.3,1.0);
            listButton[2]->bPermanent=true;
            listButton[2]->sceneShaderID="color";
            listButton[2]->setup();

            // time scale buttons
            for( int i = 3; i < 6; i++)
            {
                renderer->actorInfo["12AssignButton"].actorReference->create();
                listButton.push_back(renderer->buttonList.back());

                listButton[i]->name="";
                listButton[i]->bDrawName=true;
                listButton[i]->parent=this;
                listButton[i]->level=level+1;
                listButton[i]->tooltip="";
                listButton[i]->color=Vector4f(0.3,0.6,0.3,1.0);
                listButton[i]->bPermanent=true;
                listButton[i]->sceneShaderID="color";
                listButton[i]->setup();

            }

            listButton[3]->name="zmIn";
            listButton[4]->name="zmOut";
            listButton[5]->name="Focus";

            listButton[3]->color=Vector4f(0.5,0.6,0.3,1.0);
            listButton[4]->color=Vector4f(0.3,0.6,0.5,1.0);
            listButton[5]->color=Vector4f(0.6,0.3,0.3,1.0);

    }
    cout << "our Button list is: "<< listButton.size() <<" elements long..." << endl;
}

void TimelineInspector::placeTimelineButtons(){

    listDisplayMode=4;
    listColumns=3;
    //place getActor
    placeButton(0,0);
    //place play
    placeButton(1,1);

    //place play
    placeButton(2,2);

    //place zoomIn
    placeButton(3,3);
    //place zoomOut
    placeButton(4,4);
    //place Focus
    placeButton(5,5);



    //place timelineButtons
    for (uint i=0; i<timelineActors.size();i++){
        placeButton(i*3+6,i*3+6);
        placeButton(i*3+7,i*3+7);
        placeButton(i*3+8,i*3+8);

        listButton[8+3*i]->scale.x=600;
        listButton[8+3*i]->scale.y=15;
    }
}


void TimelineInspector::addTimeline(int i, bool bSkeletal){


            cout << input->worldTarget->name << endl;

            /** NAME **/
            //Button for displaying the actor's name
            renderer->actorInfo["6Button"].actorReference->create();
            listButton.push_back(renderer->buttonList[renderer->buttonList.size()-1]);
            //position in button list is calculated as follows:
            // i - position of actor in timelineActor list
            // *
            // 2 buttons are created for each timeline per actor -> change if more buttons are needed per timeline
            // +
            // 2 offset of all the timelineButtons, since have the "add" and "play" buttons -> change if more buttons are needed before timelines (such as pause)
            Button* nameButton=listButton[i*3+6];
            if (bSkeletal){
                nameButton->name="bones";
                nameButton->color=Vector4f(0.3,0.3,0.6,1.0);
                }
            else{
                nameButton->color=Vector4f(0.3,0.3,0.3,1.0);
                nameButton->name=timelineActors[i]->name;
                }

            nameButton->level=level+1;
            nameButton->bDrawName=true;
            nameButton->bPermanent=true;
            nameButton->parent=this;
            nameButton->sceneShaderID="color";
            nameButton->setup();

            /** MAKE ACTION **/

            renderer->actorInfo["12AssignButton"].actorReference->create();
            listButton.push_back(renderer->buttonList.back());
            //position in button list is calculated as follows:
            // i - position of actor in timelineActor list
            // *
            // 2 buttons are created for each timeline per actor -> change if more buttons are needed per timeline
            // +
            // 2 offset of all the timelineButtons, since have the "add" and "play" buttons -> change if more buttons are needed before timelines (such as pause)
            Button* makeAction=listButton[i*3+7];
            makeAction->name="make";
            makeAction->color=Vector4f(0.3,0.3,0.6,1.0);

            makeAction->level=level+1;
            makeAction->bDrawName=true;
            makeAction->bPermanent=true;
            makeAction->sceneShaderID="color";
            makeAction->parent=this;
            makeAction->setup();


            /** TIMELINE **/
            //add timeline box like in Aftereffects
            //for location and rotation -> special button
            //for skeletalactor -> for each subobject, matrixKeyFrame -> maybe convert to location/rotation
            renderer->actorInfo["14TimelineButton"].actorReference->create();
            listButton.push_back(renderer->buttonList.back());
            TimelineButton* tlBtn = (TimelineButton*)listButton[i*3+8];
            tlBtn->tooltip="Timeline for" + timelineActors[i]->name;
            tlBtn->parent=this;
            tlBtn->connectedActor=timelineActors[i];
            tlBtn->level=level+1;

            if (bSkeletal){
                tlBtn->color=Vector4f(0.6,0.6,0.8,1.0);
                tlBtn->bSkeletalTrack=true;
                }
            else
                tlBtn->color=Vector4f(0.6,0.6,0.6,1.0);
            tlBtn->bPermanent=true;
            //arbitrary, obviously needs to be relative to something...
            tlBtn->location.x=nameButton->location.x+nameButton->scale.x;
            tlBtn->location.y=nameButton->location.y;
            tlBtn->setup();

            placeTimelineButtons();
}

void TimelineInspector::trigger(Actor* other){

    //is a callback from the buttons from our list!

    cout << "triggered timelineInspector!" << endl;

    //manually create new timeline...
    if (other->name=="Add"){

        // check if we have that actor already!! or if we selected the ground
        bool bOkayToAdd = true;

        if( input->worldTarget->name == "ground")
            bOkayToAdd = false;

        for( uint i=0; i < timelineActors.size(); i++)
        {
            if( timelineActors[i] == input->worldTarget )
                bOkayToAdd = false;
        }

        if( bOkayToAdd )
        {
            int pos=0;
            if (timelineActors.size()>0)
                pos=timelineActors.size();

            //if it's a regular actor...
            SkeletalActor* skel=dynamic_cast<SkeletalActor*>(input->worldTarget);
            if (skel){
                timelineActors.push_back(input->worldTarget);
                addTimeline(pos, false);

                timelineActors.push_back(input->worldTarget);
                addTimeline(pos, true);
                }
            else{
                timelineActors.push_back(input->worldTarget);
                addTimeline(pos, false);
                }
        }
    }

    //PLAY!
    if (other->name=="play"){
      for(uint i=0;i<listButton.size();i++){
        if (listButton[i]->isA("TimelineButton")){
            ((TimelineButton*)listButton[i])->playTimeline();
        }
      }
    cout << "playing!" << endl;
    }

    //PAUSE!
    if (other==listButton[2])
      for(uint i=0;i<listButton.size();i++){
        if (listButton[i]->isA("TimelineButton")){
            ((TimelineButton*)listButton[i])->pauseTimeline();
        }
      }

    //MAKE NEW ACTION!
    if (other->name=="make"){
        TimelineButton* tlBtn;
        cout << "listSize: " << listButton.size() << endl;

        for (uint i=0;i<listButton.size();i++){
            if (other==listButton[i])
                tlBtn=(TimelineButton*)listButton[i+1];
        }

        input->staticButton=(Button*)renderer->actorInfo["18CreateActionButton"].actorReference;
        input->staticButton->location=Vector3f(input->screenX/2-200,input->screenY/2-50,0);
        input->staticButton->color=Vector4f(1.0,1.0,0.0,1.0);
        input->staticButton->name="name your action";
        input->staticButton->parent=tlBtn;
        input->staticButton->clickedLeft();
        renderer->buttonList.push_back(input->staticButton);

        other->color = Vector4f(1.0,0.0,0.0,1.0);
        other->name="connect";

    }else if (other->name=="connect"){
        TimelineButton* tlBtn;
        for (uint i=0;i<listButton.size();i++){
            if (other==listButton[i])
                tlBtn=(TimelineButton*)listButton[i+1];
        }

        //save updated action before disconnecting
        TiXmlElement* myAction = new TiXmlElement("MovieSandbox");
        //save in order of actorList for later referencing!
        myAction->LinkEndChild(tlBtn->connectedAction->save(myAction));
        TiXmlDocument doc;
        TiXmlDeclaration * decl = new TiXmlDeclaration( "1.0", "", "" );
        doc.LinkEndChild( decl );
        doc.LinkEndChild(myAction);
        string stringName="resources/actions/"+tlBtn->connectedAction->name+".action";
        doc.SaveFile(stringName);

        tlBtn->disconnectAction();
        other->color = Vector4f(0.3 , 0.3 , 0.6 , 1.0);
        other->name="make";
    }

    // ZOOM IN TIMESCALE
    if (other->name=="zmIn")
    {
        zoomTimeScale(.1f);
    }

    // ZOOM OUT TIMESCALE
    if (other->name=="zmOut")
    {
        zoomTimeScale(-.1f);
    }

}

void TimelineInspector::clickedRight(){}

void TimelineInspector::focusClick(){

    Button::focusClick();
}

void TimelineInspector::deselect(int depth){

    //ListButton::deselect(depth);
}

void TimelineInspector::create(){renderer->addButton(this);}


void TimelineInspector::zoomTimeScale( float val )
{
    timeScale += val;
    if( timeScale < .1 ) timeScale = .1;

    for(uint i=0;i<listButton.size();i++)
    {
        if (listButton[i]->isA("TimelineButton")){
            ((TimelineButton*)listButton[i])->setTimeScale(timeScale);
        }
    }
}


void TimelineInspector::removeTimeline(int i){

 timelineActors.erase(timelineActors.begin()+(i-6)/3);
 listButton[i+2]->remove();
 listButton[i+1]->remove();
 listButton[i]->remove();
 listButton.erase(listButton.begin()+i, listButton.begin()+i+3);
 placeTimelineButtons();
}
